home *** CD-ROM | disk | FTP | other *** search
/ Cream of the Crop 26 / Cream of the Crop 26.iso / doom / quake.zip / PW_DOE.ZIP / ITEMS.QC < prev    next >
Text File  |  1997-05-01  |  38KB  |  1,713 lines

  1. void() W_SetCurrentAmmo;
  2. /* ALL LIGHTS SHOULD BE 0 1 0 IN COLOR ALL OTHER ITEMS SHOULD
  3. BE .8 .3 .4 IN COLOR */
  4.  
  5.  
  6. void() SUB_regen =
  7. {
  8.     self.model = self.mdl;        // restore original model
  9.     self.solid = SOLID_TRIGGER;    // allow it to be touched again
  10.     sound (self, CHAN_VOICE, "items/itembk2.wav", 1, ATTN_NORM);    // play respawn sound
  11.     setorigin (self, self.origin);
  12. };
  13.  
  14.  
  15.  
  16. /*QUAKED noclass (0 0 0) (-8 -8 -8) (8 8 8)
  17. prints a warning message when spawned
  18. */
  19. void() noclass =
  20. {
  21.     dprint ("noclass spawned at");
  22.     dprint (vtos(self.origin));
  23.     dprint ("\n");
  24.     remove (self);
  25. };
  26.  
  27.  
  28.  
  29. /*
  30. ============
  31. PlaceItem
  32.  
  33. plants the object on the floor
  34. ============
  35. */
  36. void() PlaceItem =
  37. {
  38.     local float    oldz;
  39.  
  40.     self.mdl = self.model;        // so it can be restored on respawn
  41.     self.flags = FL_ITEM;        // make extra wide
  42.     self.solid = SOLID_TRIGGER;
  43.     self.movetype = MOVETYPE_TOSS;    
  44.     self.velocity = '0 0 0';
  45.     self.origin_z = self.origin_z + 6;
  46.     oldz = self.origin_z;
  47.     if (!droptofloor())
  48.     {
  49.         dprint ("Bonus item fell out of level!\n");
  50.         dprint (self.classname);
  51.         dprint (" at ");
  52.         dprint (vtos(self.origin));
  53.         dprint ("\n");
  54.         remove(self);
  55.         return;
  56.     }
  57. };
  58.  
  59. /*
  60. ============
  61. StartItem
  62.  
  63. Sets the clipping size and plants the object on the floor
  64. ============
  65. */
  66. void() StartItem =
  67. {
  68.     self.nextthink = time + 0.2;    // items start after other solids
  69.     self.think = PlaceItem;
  70. };
  71.  
  72. /*
  73. =========================================================================
  74.  
  75. HEALTH BOX
  76.  
  77. =========================================================================
  78. */
  79. //
  80. // T_Heal: add health to an entity, limiting health to max_health
  81. // "ignore" will ignore max_health limit
  82. //
  83. float (entity e, float healamount, float ignore) T_Heal =
  84. {
  85.     if (e.health <= 0)
  86.         return 0;
  87.     if ((!ignore) && (e.health >= other.max_health))
  88.         return 0;
  89.     healamount = ceil(healamount);
  90.  
  91.     e.health = e.health + healamount;
  92.     if ((!ignore) && (e.health >= other.max_health))
  93.         e.health = other.max_health;
  94.         
  95.     if (e.health > 250)
  96.         e.health = 250;
  97.     return 1;
  98. };
  99.  
  100. /*QUAKED item_health (.3 .3 1) (0 0 0) (32 32 32) rotten megahealth
  101. Health box. Normally gives 25 points.
  102. Rotten box heals 5-10 points,
  103. megahealth will add 100 health, then 
  104. rot you down to your maximum health limit, 
  105. one point per second.
  106. */
  107.  
  108. float    H_ROTTEN = 1;
  109. float    H_MEGA = 2;
  110. .float    healamount, healtype;
  111. void() health_touch;
  112. void() item_megahealth_rot;
  113.  
  114. void() item_health =
  115. {    
  116.     self.touch = health_touch;
  117.  
  118.     if (self.spawnflags & H_ROTTEN)
  119.     {
  120.         precache_model("maps/b_bh10.bsp");
  121.  
  122.         precache_sound("items/r_item1.wav");
  123.         setmodel(self, "maps/b_bh10.bsp");
  124.         self.noise = "items/r_item1.wav";
  125.         self.healamount = 15;
  126.         self.healtype = 0;
  127.     }
  128.     else
  129.     if (self.spawnflags & H_MEGA)
  130.     {
  131.         precache_model("maps/b_bh100.bsp");
  132.         precache_sound("items/r_item2.wav");
  133.         setmodel(self, "maps/b_bh100.bsp");
  134.         self.noise = "items/r_item2.wav";
  135.         self.healamount = 100;
  136.         self.healtype = 2;
  137.     }
  138.     else
  139.     {
  140.         precache_model("maps/b_bh25.bsp");
  141.         precache_sound("items/health1.wav");
  142.         setmodel(self, "maps/b_bh25.bsp");
  143.         self.noise = "items/health1.wav";
  144.         self.healamount = 25;
  145.         self.healtype = 1;
  146.     }
  147.     setsize (self, '0 0 0', '32 32 56');
  148.     StartItem ();
  149. };
  150.  
  151.  
  152. void() health_touch =
  153. {
  154.     local    float amount;
  155.     local    string    s;
  156.     
  157.     if (other.classname != "player")
  158.         return;
  159.     
  160.     if (self.healtype == 2) // Megahealth?  Ignore max_health...
  161.     {
  162.         if (other.health >= 250)
  163.             return;
  164.         if (!T_Heal(other, self.healamount, 1))
  165.             return;
  166.     }
  167.     else
  168.     {
  169.         if (!T_Heal(other, self.healamount, 0))
  170.             return;
  171.     }
  172.     
  173.     sprint(other, "You receive ");
  174.     s = ftos(self.healamount);
  175.     sprint(other, s);
  176.     sprint(other, " health\n");
  177.     
  178. // health touch sound
  179.     sound(other, CHAN_ITEM, self.noise, 1, ATTN_NORM);
  180.  
  181.     stuffcmd (other, "bf\n");
  182.     
  183.     self.model = string_null;
  184.     self.solid = SOLID_NOT;
  185.  
  186.     // Megahealth = rot down the player's super health
  187.     if (self.healtype == 2 && !RuneHasElder(other))
  188.     {
  189.         other.items2 = other.items2 | IT2_SUPERHEALTH;
  190.         self.nextthink = time + 5;
  191.         self.think = item_megahealth_rot;
  192.         self.owner = other;
  193.     }
  194.     else
  195.     {
  196.         if (deathmatch != 2)        // deathmatch 2 is the silly old rules
  197.         {
  198.             if (deathmatch)
  199.                 self.nextthink = time + 20;
  200.             self.think = SUB_regen;
  201.         }
  202.     }
  203.     
  204.     activator = other;
  205.     SUB_UseTargets();                // fire all targets / killtargets
  206. };    
  207.  
  208. void() item_megahealth_rot =
  209. {
  210.     other = self.owner;
  211.     
  212.     if (other.health > other.max_health)
  213.     {
  214.         other.health = other.health - 1;
  215.         self.nextthink = time + 1;
  216.         return;
  217.     }
  218.  
  219. // it is possible for a player to die and respawn between rots, so don't
  220. // just blindly subtract the flag off
  221.     other.items2 = other.items2 - (other.items2 & IT2_SUPERHEALTH);
  222.     
  223.     if (deathmatch == 1)    // deathmatch 2 is silly old rules
  224.     {
  225.         self.nextthink = time + 20;
  226.         self.think = SUB_regen;
  227.     }
  228. };
  229.  
  230. /*
  231. ===============================================================================
  232.  
  233. ARMOR
  234.  
  235. ===============================================================================
  236. */
  237.  
  238. void() armor_touch;
  239.  
  240. void() armor_touch =
  241. {
  242.     local    float    type, value, bit;
  243.     
  244.     if (other.health <= 0)
  245.         return;
  246.     if (other.classname != "player")
  247.         return;
  248.  
  249.     if (self.classname == "item_armor1")
  250.     {
  251.         type = 0.3;
  252.         value = 100;
  253.         bit = IT2_ARMOR1;
  254.     }
  255.     if (self.classname == "item_armor2")
  256.     {
  257.         type = 0.6;
  258.         value = 150;
  259.         bit = IT2_ARMOR2;
  260.     }
  261.     if (self.classname == "item_armorInv")
  262.     {
  263.         type = 0.8;
  264.         value = 200;
  265.         bit = IT2_ARMOR3;
  266.     }
  267.     if (other.armortype*other.armorvalue >= type*value)
  268.         return;
  269.         
  270.     other.armortype = type;
  271.     other.armorvalue = value;
  272.     other.items2 = other.items2 - 
  273.                 (other.items2 & (IT2_ARMOR1 | IT2_ARMOR2 | IT2_ARMOR3)) + bit;
  274.  
  275.     self.solid = SOLID_NOT;
  276.     self.model = string_null;
  277.     if (deathmatch == 1)
  278.         self.nextthink = time + 20;
  279.     self.think = SUB_regen;
  280.  
  281.     sprint(other, "You got armor\n");
  282. // armor touch sound
  283.     sound(other, CHAN_ITEM, "items/armor1.wav", 1, ATTN_NORM);
  284.     stuffcmd (other, "bf\n");
  285.     
  286.     activator = other;
  287.     SUB_UseTargets();                // fire all targets / killtargets
  288. };
  289.  
  290.  
  291. /*QUAKED item_armor1 (0 .5 .8) (-16 -16 0) (16 16 32)
  292. */
  293.  
  294. void() item_armor1 =
  295. {
  296.     self.touch = armor_touch;
  297.     precache_model ("progs/armor.mdl");
  298.     setmodel (self, "progs/armor.mdl");
  299.     self.skin = 0;
  300.     setsize (self, '-16 -16 0', '16 16 56');
  301.     StartItem ();
  302. };
  303.  
  304. /*QUAKED item_armor2 (0 .5 .8) (-16 -16 0) (16 16 32)
  305. */
  306.  
  307. void() item_armor2 =
  308. {
  309.     self.touch = armor_touch;
  310.     precache_model ("progs/armor.mdl");
  311.     setmodel (self, "progs/armor.mdl");
  312.     self.skin = 1;
  313.     setsize (self, '-16 -16 0', '16 16 56');
  314.     StartItem ();
  315. };
  316.  
  317. /*QUAKED item_armorInv (0 .5 .8) (-16 -16 0) (16 16 32)
  318. */
  319.  
  320. void() item_armorInv =
  321. {
  322.     self.touch = armor_touch;
  323.     precache_model ("progs/armor.mdl");
  324.     setmodel (self, "progs/armor.mdl");
  325.     self.skin = 2;
  326.     setsize (self, '-16 -16 0', '16 16 56');
  327.     StartItem ();
  328. };
  329.  
  330. /*
  331. ===============================================================================
  332.  
  333. WEAPONS
  334.  
  335. ===============================================================================
  336. */
  337.  
  338. void() bound_other_ammo =
  339. {
  340.     if (other.ammo_shells1 > 100)
  341.         other.ammo_shells1 = 100;
  342.     if (other.ammo_nails1 > 200)
  343.         other.ammo_nails1 = 200;
  344.     if (other.ammo_rockets1 > 100)
  345.         other.ammo_rockets1 = 100;        
  346.     if (other.ammo_cells1 > 100)
  347.         other.ammo_cells1 = 100;        
  348.         
  349.     // PGM addition
  350.     if (other.ammo_lava_nails > 200)
  351.         other.ammo_lava_nails = 200;
  352.     if (other.ammo_multi_rockets > 100)
  353.         other.ammo_multi_rockets = 100;
  354.     if (other.ammo_plasma > 100)
  355.         other.ammo_plasma = 100;
  356. };
  357.  
  358.  
  359. float(float w) RankForWeapon =
  360. {
  361.     if (w == IT_PLASMA_GUN)
  362.         return 1;
  363.     if (w == IT_LIGHTNING)
  364.         return 2;
  365.     if (w == IT_MULTI_ROCKET)
  366.         return 3;
  367.     if (w == IT_ROCKET_LAUNCHER)
  368.         return 4;
  369.     if (w == IT_LAVA_SUPER_NAILGUN)
  370.         return 5;
  371.     if (w == IT_SUPER_NAILGUN)
  372.         return 6;
  373.     if (w == IT_MULTI_GRENADE)
  374.         return 7;
  375.     if (w == IT_GRENADE_LAUNCHER)
  376.         return 8;
  377.     if (w == IT_LAVA_NAILGUN)
  378.         return 9;
  379.     if (w == IT_SUPER_SHOTGUN)
  380.         return 10;
  381.     if (w == IT_NAILGUN)
  382.         return 11;
  383.     return 12;
  384. };
  385.  
  386. /*
  387. =============
  388. Deathmatch_Weapon
  389.  
  390. Deathmatch weapon change rules for picking up a weapon
  391.  
  392. .float        ammo_shells1, ammo_nails1, ammo_rockets1, ammo_cells1;
  393. =============
  394. */
  395. void(float old, float new) Deathmatch_Weapon =
  396. {
  397.     local float or, nr;
  398.  
  399. // PGM - fix for changing to weapons when grappling.
  400.     if (self.weapon == IT_GRAPPLE && self.button0)
  401.         return;
  402.  
  403. // change self.weapon if desired
  404.     or = RankForWeapon (self.weapon);
  405.     nr = RankForWeapon (new);
  406.     if ( nr < or )
  407.         self.weapon = new;
  408. };
  409.  
  410. void(entity comboOwner) EnableComboWeapons =
  411. {
  412.     if (comboOwner.classname != "player")
  413.         return;
  414.     
  415.     if (!(comboOwner.items & IT_LAVA_NAILGUN))
  416.     {
  417.         if (comboOwner.ammo_lava_nails > 0 && (comboOwner.items & IT_NAILGUN))
  418.         {
  419.             sprint (comboOwner, "Lava Enabled\n");
  420.             comboOwner.items = comboOwner.items | IT_LAVA_NAILGUN;
  421.         }
  422.     }
  423.  
  424.     if (!(comboOwner.items & IT_LAVA_SUPER_NAILGUN))
  425.     {
  426.         if (comboOwner.ammo_lava_nails > 0 && 
  427.                             (comboOwner.items & IT_SUPER_NAILGUN))
  428.         {
  429.             sprint (comboOwner, "Super Lava Enabled\n");
  430.             comboOwner.items = comboOwner.items | IT_LAVA_SUPER_NAILGUN;        
  431.         }
  432.     }
  433.  
  434.     if (!(comboOwner.items & IT_MULTI_GRENADE))
  435.     {
  436.         if (comboOwner.ammo_multi_rockets > 0 && 
  437.                             (comboOwner.items & IT_GRENADE_LAUNCHER))
  438.         {
  439.             sprint (comboOwner, "Multi Grenades Enabled\n");
  440.             comboOwner.items = comboOwner.items | IT_MULTI_GRENADE;        
  441.         }
  442.     }
  443.  
  444.     if (!(comboOwner.items & IT_MULTI_ROCKET))
  445.     {
  446.         if (comboOwner.ammo_multi_rockets > 0 && 
  447.                             (comboOwner.items & IT_ROCKET_LAUNCHER))
  448.         {
  449.             sprint (comboOwner, "Multi Rockets Enabled\n");
  450.             comboOwner.items = comboOwner.items | IT_MULTI_ROCKET;        
  451.         }
  452.     }
  453.  
  454.     if (!(comboOwner.items & IT_PLASMA_GUN))
  455.     {
  456.         if (comboOwner.ammo_plasma > 0 && (comboOwner.items & IT_LIGHTNING))
  457.         {
  458.             sprint (comboOwner, "Plasma Gun Enabled\n");
  459.             comboOwner.items = comboOwner.items | IT_PLASMA_GUN;        
  460.         }
  461.     }
  462. };
  463.  
  464. /*
  465. =============
  466. weapon_touch
  467. =============
  468. */
  469. float() W_BestWeapon;
  470.  
  471. void() weapon_touch =
  472. {
  473.     local    float    hadammo, best, new, old;
  474.     local    entity    stemp;
  475.     local    float    leave;
  476. // from McBain: local previous weapon variable -geezer
  477.     local    float    prevweapon;
  478.  
  479.     if (!(other.flags & FL_CLIENT))
  480.         return;
  481.  
  482. // if the player was using his best weapon, change up to the new one if better        
  483.     stemp = self;
  484.     self = other;
  485.     best = W_BestWeapon();
  486.     self = stemp;
  487.  
  488.     if (deathmatch == 2 || coop)
  489.         leave = 1;
  490.     else
  491.         leave = 0;
  492.     
  493.     if (self.classname == "weapon_nailgun")
  494.     {
  495.         if (leave && (other.items & IT_NAILGUN) )
  496.             return;
  497.         hadammo = other.ammo_nails1;            
  498.         new = IT_NAILGUN;
  499.         if (leave)
  500.             other.ammo_lava_nails = other.ammo_lava_nails + 20;
  501.         other.ammo_nails1 = other.ammo_nails1 + 30;
  502.     }
  503.     else if (self.classname == "weapon_supernailgun")
  504.     {
  505.         if (leave && (other.items & IT_SUPER_NAILGUN) )
  506.             return;
  507.         hadammo = other.ammo_rockets1;            
  508.         new = IT_SUPER_NAILGUN;
  509.         if (leave)
  510.             other.ammo_lava_nails = other.ammo_lava_nails + 20;
  511.         other.ammo_nails1 = other.ammo_nails1 + 30;
  512.     }
  513.     else if (self.classname == "weapon_supershotgun")
  514.     {
  515.         if (leave && (other.items & IT_SUPER_SHOTGUN) )
  516.             return;
  517.         hadammo = other.ammo_rockets1;            
  518.         new = IT_SUPER_SHOTGUN;
  519.         other.ammo_shells1 = other.ammo_shells1 + 5;
  520.     }
  521.     else if (self.classname == "weapon_rocketlauncher")
  522.     {
  523.         if (leave && (other.items & IT_ROCKET_LAUNCHER) )
  524.             return;
  525.         hadammo = other.ammo_rockets1;            
  526.         new = IT_ROCKET_LAUNCHER;
  527.         if (leave)
  528.             other.ammo_multi_rockets = other.ammo_multi_rockets + 3;
  529.         other.ammo_rockets1 = other.ammo_rockets1 + 5;
  530.     }
  531.     else if (self.classname == "weapon_grenadelauncher")
  532.     {
  533.         if (leave && (other.items & IT_GRENADE_LAUNCHER) )
  534.             return;
  535.         hadammo = other.ammo_rockets1;            
  536.         new = IT_GRENADE_LAUNCHER;
  537.         if (leave)
  538.             other.ammo_multi_rockets = other.ammo_multi_rockets + 3;
  539.         other.ammo_rockets1 = other.ammo_rockets1 + 5;
  540.     }
  541.     else if (self.classname == "weapon_lightning")
  542.     {
  543.         if (leave && (other.items & IT_LIGHTNING) )
  544.             return;
  545.         hadammo = other.ammo_rockets1;            
  546.         new = IT_LIGHTNING;
  547.         if (leave)
  548.             other.ammo_plasma = other.ammo_plasma + 5;
  549.         other.ammo_cells1 = other.ammo_cells1 + 15;
  550.     }
  551.     else
  552.         objerror ("weapon_touch: unknown classname");
  553.  
  554.     sprint (other, "You got the ");
  555.     sprint (other, self.netname);
  556.     sprint (other, "\n");
  557. // weapon touch sound
  558.     sound (other, CHAN_ITEM, "weapons/pkup.wav", 1, ATTN_NORM);
  559.     stuffcmd (other, "bf\n");
  560.  
  561.     bound_other_ammo ();
  562.  
  563. // change to the weapon
  564.     old = other.items;
  565.     other.items = other.items | new;
  566.  
  567.     EnableComboWeapons ( other );
  568.  
  569.     // PGM - fake picking up the plasma gun.
  570.     if (new == IT_LIGHTNING)
  571.     {
  572.         if (other.ammo_plasma > 0)
  573.             new = IT_PLASMA_GUN;
  574.     }
  575.     else if (new == IT_ROCKET_LAUNCHER)
  576.     {
  577.         if (other.ammo_multi_rockets > 0)
  578.             new = IT_MULTI_ROCKET;
  579.     }
  580.     else if (new == IT_GRENADE_LAUNCHER)
  581.     {
  582.         if (other.ammo_multi_rockets > 0)
  583.             new = IT_MULTI_GRENADE;
  584.     }
  585.     else if (new == IT_SUPER_NAILGUN)
  586.     {
  587.         if (other.ammo_lava_nails > 1)
  588.             new = IT_LAVA_SUPER_NAILGUN;
  589.     }
  590.     else if (new == IT_NAILGUN)
  591.     {
  592.         if (other.ammo_lava_nails > 0)
  593.             new = IT_LAVA_NAILGUN;
  594.     }
  595.     
  596.     
  597.     stemp = self;
  598.     self = other;
  599.  
  600. // from McBain:  temp store old weapon   -geezer
  601.     prevweapon = self.weapon;
  602.  
  603.     if (!deathmatch)
  604.         self.weapon = new;
  605.     else
  606.         Deathmatch_Weapon (old, new);
  607.  
  608. // from McBain:  save previous weapon if different   -geezer
  609.     if (self.weapon != prevweapon)
  610.         self.previous_weapon = prevweapon;
  611.  
  612.     UpdateAmmoCounts ( self );
  613.     W_SetCurrentAmmo();
  614.  
  615.     self = stemp;
  616.  
  617.     if (leave)
  618.         return;
  619.  
  620. // remove it in single player, or setup for respawning in deathmatch
  621.     self.model = string_null;
  622.     self.solid = SOLID_NOT;
  623.     if (deathmatch == 1)
  624.          self.nextthink = time + 30;
  625.     self.think = SUB_regen;
  626.     
  627.     activator = other;
  628.     SUB_UseTargets();                // fire all targets / killtargets
  629. };
  630.  
  631.  
  632. /*QUAKED weapon_supershotgun (0 .5 .8) (-16 -16 0) (16 16 32)
  633. */
  634.  
  635. void() weapon_supershotgun =
  636. {
  637.     precache_model ("progs/g_shot.mdl");
  638.     setmodel (self, "progs/g_shot.mdl");
  639.     self.weapon = IT_SUPER_SHOTGUN;
  640.     self.netname = "Double-barrelled Shotgun";
  641.     self.touch = weapon_touch;
  642.     setsize (self, '-16 -16 0', '16 16 56');
  643.     StartItem ();
  644. };
  645.  
  646. /*QUAKED weapon_nailgun (0 .5 .8) (-16 -16 0) (16 16 32)
  647. */
  648.  
  649. void() weapon_nailgun =
  650. {
  651.     precache_model ("progs/g_nail.mdl");
  652.     setmodel (self, "progs/g_nail.mdl");
  653.     self.weapon = IT_NAILGUN;
  654.     self.netname = "nailgun";
  655.     self.touch = weapon_touch;
  656.     setsize (self, '-16 -16 0', '16 16 56');
  657.     StartItem ();
  658. };
  659.  
  660. /*QUAKED weapon_supernailgun (0 .5 .8) (-16 -16 0) (16 16 32)
  661. */
  662.  
  663. void() weapon_supernailgun =
  664. {
  665.     precache_model ("progs/g_nail2.mdl");
  666.     setmodel (self, "progs/g_nail2.mdl");
  667.     self.weapon = IT_SUPER_NAILGUN;
  668.     self.netname = "Super Nailgun";
  669.     self.touch = weapon_touch;
  670.     setsize (self, '-16 -16 0', '16 16 56');
  671.     StartItem ();
  672. };
  673.  
  674. /*QUAKED weapon_grenadelauncher (0 .5 .8) (-16 -16 0) (16 16 32)
  675. */
  676.  
  677. void() weapon_grenadelauncher =
  678. {
  679.     precache_model ("progs/g_rock.mdl");
  680.     setmodel (self, "progs/g_rock.mdl");
  681.     self.weapon = 3;
  682.     self.netname = "Grenade Launcher";
  683.     self.touch = weapon_touch;
  684.     setsize (self, '-16 -16 0', '16 16 56');
  685.     StartItem ();
  686. };
  687.  
  688. /*QUAKED weapon_rocketlauncher (0 .5 .8) (-16 -16 0) (16 16 32)
  689. */
  690.  
  691. void() weapon_rocketlauncher =
  692. {
  693.     precache_model ("progs/g_rock2.mdl");
  694.     setmodel (self, "progs/g_rock2.mdl");
  695.     self.weapon = 3;
  696.     self.netname = "Rocket Launcher";
  697.     self.touch = weapon_touch;
  698.     setsize (self, '-16 -16 0', '16 16 56');
  699.     StartItem ();
  700. };
  701.  
  702.  
  703. /*QUAKED weapon_lightning (0 .5 .8) (-16 -16 0) (16 16 32)
  704. */
  705.  
  706. void() weapon_lightning =
  707. {
  708.     precache_model ("progs/g_light.mdl");
  709.     setmodel (self, "progs/g_light.mdl");
  710.     self.weapon = 3;
  711.     self.netname = "Thunderbolt";
  712.     self.touch = weapon_touch;
  713.     setsize (self, '-16 -16 0', '16 16 56');
  714.     StartItem ();
  715. };
  716.  
  717.  
  718. /*
  719. ===============================================================================
  720.  
  721. AMMO
  722.  
  723. ===============================================================================
  724. */
  725.  
  726. void() ammo_touch =
  727. {
  728. local entity    stemp;
  729. local float        best;
  730.  
  731.     if (other.classname != "player")
  732.         return;
  733.     if (other.health <= 0)
  734.         return;
  735.  
  736. // if the player was using his best weapon, change up to the new one if better        
  737.  
  738.     stemp = self;
  739.     self = other;
  740.     best = W_BestWeapon();
  741.     self = stemp;
  742.  
  743. // by this point, other is the player and self is the ammo pack. - PGM
  744.  
  745. // shotgun
  746.     if (self.weapon == 1)
  747.     {
  748.         if (other.ammo_shells1 >= 100)
  749.             return;
  750.         other.ammo_shells1 = other.ammo_shells1 + self.aflag;
  751.     }
  752.  
  753. // spikes
  754.     if (self.weapon == 2)
  755.     {
  756.         if (other.ammo_nails1 >= 200)
  757.             return;
  758.         other.ammo_nails1 = other.ammo_nails1 + self.aflag;
  759.     }
  760.  
  761. //    rockets
  762.     if (self.weapon == 3)
  763.     {
  764.         if (other.ammo_rockets1 >= 100)
  765.             return;
  766.         other.ammo_rockets1 = other.ammo_rockets1 + self.aflag;
  767.     }
  768.  
  769. //    cells
  770.     if (self.weapon == 4)
  771.     {
  772.         if (other.ammo_cells1 >= 100)
  773.             return;
  774.         other.ammo_cells1 = other.ammo_cells1 + self.aflag;
  775.     }
  776.  
  777. //    lava spikes
  778.     if (self.weapon == 5)
  779.     {
  780.         if(other.ammo_lava_nails >= 200)
  781.             return;            
  782.         other.ammo_lava_nails = other.ammo_lava_nails + self.aflag;
  783.     }
  784.  
  785. //    multi grenades
  786.     if (self.weapon == 6)
  787.     {
  788.         if(other.ammo_multi_rockets >= 100)
  789.             return;
  790.         other.ammo_multi_rockets = other.ammo_multi_rockets + self.aflag;
  791.     }
  792.  
  793. //    plasma
  794.     if (self.weapon == 7)
  795.     {
  796.         if(other.ammo_plasma >= 100)
  797.             return;
  798.         other.ammo_plasma = other.ammo_plasma + self.aflag;
  799.     }
  800.  
  801.     EnableComboWeapons ( other );
  802.     UpdateAmmoCounts ( other );
  803.     
  804.     bound_other_ammo ();
  805.     
  806.     sprint (other, "You got the ");
  807.     sprint (other, self.netname);
  808.     sprint (other, "\n");
  809. // ammo touch sound
  810.     sound (other, CHAN_ITEM, "weapons/lock4.wav", 1, ATTN_NORM);
  811.     stuffcmd (other, "bf\n");
  812.  
  813. // change to a better weapon if appropriate
  814.  
  815.     if ( other.weapon == best )
  816.     {
  817.         stemp = self;
  818.         self = other;
  819.         self.weapon = W_BestWeapon();
  820.         W_SetCurrentAmmo ();
  821.         self = stemp;
  822.     }
  823.  
  824. // if changed current ammo, update it
  825.     stemp = self;
  826.     self = other;
  827.     W_SetCurrentAmmo();
  828.     self = stemp;
  829.  
  830. // remove it in single player, or setup for respawning in deathmatch
  831.     self.model = string_null;
  832.     self.solid = SOLID_NOT;
  833.     if (deathmatch == 1)
  834.         self.nextthink = time + 30;    
  835.     self.think = SUB_regen;
  836.  
  837.     activator = other;
  838.     SUB_UseTargets();                // fire all targets / killtargets
  839. };
  840.  
  841.  
  842.  
  843.  
  844. float WEAPON_BIG2 = 1;
  845.  
  846. /*QUAKED item_shells (0 .5 .8) (0 0 0) (32 32 32) big
  847. Small box is 20, Big box is 40.
  848. */
  849.  
  850. void() item_shells =
  851. {
  852.     self.touch = ammo_touch;
  853.  
  854.     if (self.spawnflags & WEAPON_BIG2)
  855.     {
  856.         precache_model ("maps/b_shell1.bsp");
  857.         setmodel (self, "maps/b_shell1.bsp");
  858.         self.aflag = 40;
  859.     }
  860.     else
  861.     {
  862.         precache_model ("maps/b_shell0.bsp");
  863.         setmodel (self, "maps/b_shell0.bsp");
  864.         self.aflag = 20;
  865.     }
  866.     self.weapon = 1;
  867.     self.netname = "shells";
  868.     setsize (self, '0 0 0', '32 32 56');
  869.     StartItem ();
  870. };
  871.  
  872. /*QUAKED item_spikes (0 .5 .8) (0 0 0) (32 32 32) big
  873. Small box is 25, Big box is 50.
  874. */
  875.  
  876. void() item_spikes =
  877. {
  878.     self.touch = ammo_touch;
  879.  
  880.     if (self.spawnflags & WEAPON_BIG2)
  881.     {
  882.         precache_model ("maps/b_nail1.bsp");
  883.         setmodel (self, "maps/b_nail1.bsp");
  884.         self.aflag = 50;
  885.     }
  886.     else
  887.     {
  888.         precache_model ("maps/b_nail0.bsp");
  889.         setmodel (self, "maps/b_nail0.bsp");
  890.         self.aflag = 25;
  891.     }
  892.     self.weapon = 2;
  893.     self.netname = "nails";
  894.     setsize (self, '0 0 0', '32 32 56');
  895.     StartItem ();
  896. };
  897.  
  898. /*QUAKED item_lava_spikes (0 .5 .8) (0 0 0) (32 32 32) big
  899. Small box is 25, Big box is 50.
  900. */
  901.  
  902. void() item_lava_spikes =
  903. {
  904.     self.touch = ammo_touch;
  905.  
  906.     if (self.spawnflags & WEAPON_BIG2)
  907.     {
  908.         precache_model ("maps/b_lnail1.bsp");
  909.         setmodel (self, "maps/b_lnail1.bsp");
  910.         self.aflag = 50;
  911.     }
  912.     else
  913.     {
  914.         precache_model ("maps/b_lnail0.bsp");
  915.         setmodel (self, "maps/b_lnail0.bsp");
  916.         self.aflag = 25;
  917.     }
  918.     self.weapon = 5;
  919.     self.netname = "lava nails";
  920.     setsize (self, '0 0 0', '32 32 56');
  921.     StartItem ();
  922. };
  923.  
  924. /*QUAKED item_rockets (0 .5 .8) (0 0 0) (32 32 32) big
  925. Small box is 5, Big box is 10.
  926. */
  927.  
  928. void() item_rockets =
  929. {
  930.     self.touch = ammo_touch;
  931.  
  932.     if (self.spawnflags & WEAPON_BIG2)
  933.     {
  934.         precache_model ("maps/b_rock1.bsp");
  935.         setmodel (self, "maps/b_rock1.bsp");
  936.         self.aflag = 10;
  937.     }
  938.     else
  939.     {
  940.         precache_model ("maps/b_rock0.bsp");
  941.         setmodel (self, "maps/b_rock0.bsp");
  942.         self.aflag = 5;
  943.     }
  944.     self.weapon = 3;
  945.     self.netname = "rockets";
  946.     setsize (self, '0 0 0', '32 32 56');
  947.     StartItem ();
  948. };
  949.  
  950. /*QUAKED item_multi_rockets (0 .5 .8) (0 0 0) (32 32 32) big
  951. Small box is 5, Big box is 10.
  952. */
  953.  
  954. void() item_multi_rockets =
  955. {
  956.     self.touch = ammo_touch;
  957.  
  958.     if (self.spawnflags & WEAPON_BIG2)
  959.     {
  960.         precache_model ("maps/b_mrock1.bsp");
  961.         setmodel (self, "maps/b_mrock1.bsp");
  962.         self.aflag = 10;
  963.     }
  964.     else
  965.     {
  966.         precache_model ("maps/b_mrock0.bsp");
  967.         setmodel (self, "maps/b_mrock0.bsp");
  968.         self.aflag = 5;
  969.     }
  970.     self.weapon = 6;
  971.     self.netname = "multi rockets";
  972.     setsize (self, '0 0 0', '32 32 56');
  973.     StartItem ();
  974. };
  975.  
  976.  
  977. /*QUAKED item_cells (0 .5 .8) (0 0 0) (32 32 32) big
  978. Small box is 6, Big box is 12.
  979. */
  980. void() item_cells =
  981. {
  982.     self.touch = ammo_touch;
  983.  
  984.     if (self.spawnflags & WEAPON_BIG2)
  985.     {
  986.         precache_model ("maps/b_batt1.bsp");
  987.         setmodel (self, "maps/b_batt1.bsp");
  988.         self.aflag = 12;
  989.     }
  990.     else
  991.     {
  992.         precache_model ("maps/b_batt0.bsp");
  993.         setmodel (self, "maps/b_batt0.bsp");
  994.         self.aflag = 6;
  995.     }
  996.     self.weapon = 4;
  997.     self.netname = "cells";
  998.     setsize (self, '0 0 0', '32 32 56');
  999.     StartItem ();
  1000. };
  1001.  
  1002. /*QUAKED item_plasma (0 .5 .8) (0 0 0) (32 32 32) big
  1003. Small box is 6, Big box is 12.
  1004. */
  1005. void() item_plasma =
  1006. {
  1007.     self.touch = ammo_touch;
  1008.  
  1009.     if (self.spawnflags & WEAPON_BIG2)
  1010.     {
  1011.         precache_model ("maps/b_plas1.bsp");
  1012.         setmodel (self, "maps/b_plas1.bsp");
  1013.         self.aflag = 12;
  1014.     }
  1015.     else
  1016.     {
  1017.         precache_model ("maps/b_plas0.bsp");
  1018.         setmodel (self, "maps/b_plas0.bsp");
  1019.         self.aflag = 6;
  1020.     }
  1021.     self.weapon = 7;
  1022.     self.netname = "plasma";
  1023.     setsize (self, '0 0 0', '32 32 56');
  1024.     StartItem ();
  1025. };
  1026.  
  1027.  
  1028. /*QUAKED item_weapon (0 .5 .8) (0 0 0) (32 32 32) shotgun rocket spikes big
  1029. DO NOT USE THIS!!!! IT WILL BE REMOVED!
  1030. */
  1031.  
  1032. float WEAPON_SHOTGUN = 1;
  1033. float WEAPON_ROCKET = 2;
  1034. float WEAPON_SPIKES = 4;
  1035. float WEAPON_BIG = 8;
  1036. void() item_weapon =
  1037. {
  1038.     self.touch = ammo_touch;
  1039.  
  1040.     if (self.spawnflags & WEAPON_SHOTGUN)
  1041.     {
  1042.         if (self.spawnflags & WEAPON_BIG)
  1043.         {
  1044.             precache_model ("maps/b_shell1.bsp");
  1045.             setmodel (self, "maps/b_shell1.bsp");
  1046.             self.aflag = 40;
  1047.         }
  1048.         else
  1049.         {
  1050.             precache_model ("maps/b_shell0.bsp");
  1051.             setmodel (self, "maps/b_shell0.bsp");
  1052.             self.aflag = 20;
  1053.         }
  1054.         self.weapon = 1;
  1055.         self.netname = "shells";
  1056.     }
  1057.  
  1058.     if (self.spawnflags & WEAPON_SPIKES)
  1059.     {
  1060.         if (self.spawnflags & WEAPON_BIG)
  1061.         {
  1062.             precache_model ("maps/b_nail1.bsp");
  1063.             setmodel (self, "maps/b_nail1.bsp");
  1064.             self.aflag = 40;
  1065.         }
  1066.         else
  1067.         {
  1068.             precache_model ("maps/b_nail0.bsp");
  1069.             setmodel (self, "maps/b_nail0.bsp");
  1070.             self.aflag = 20;
  1071.         }
  1072.         self.weapon = 2;
  1073.         self.netname = "spikes";
  1074.     }
  1075.  
  1076.     if (self.spawnflags & WEAPON_ROCKET)
  1077.     {
  1078.         if (self.spawnflags & WEAPON_BIG)
  1079.         {
  1080.             precache_model ("maps/b_rock1.bsp");
  1081.             setmodel (self, "maps/b_rock1.bsp");
  1082.             self.aflag = 10;
  1083.         }
  1084.         else
  1085.         {
  1086.             precache_model ("maps/b_rock0.bsp");
  1087.             setmodel (self, "maps/b_rock0.bsp");
  1088.             self.aflag = 5;
  1089.         }
  1090.         self.weapon = 3;
  1091.         self.netname = "rockets";
  1092.     }
  1093.     
  1094.     setsize (self, '0 0 0', '32 32 56');
  1095.     StartItem ();
  1096. };
  1097.  
  1098.  
  1099. /*
  1100. ===============================================================================
  1101.  
  1102. KEYS
  1103.  
  1104. ===============================================================================
  1105. */
  1106.  
  1107. void() key_touch =
  1108. {
  1109. local entity    stemp;
  1110. local float        best;
  1111.  
  1112.     if (other.classname != "player")
  1113.         return;
  1114.     if (other.health <= 0)
  1115.         return;
  1116.     if (other.items & self.items)
  1117.         return;
  1118.  
  1119.     sprint (other, "You got the ");
  1120.     sprint (other, self.netname);
  1121.     sprint (other,"\n");
  1122.  
  1123.     sound (other, CHAN_ITEM, self.noise, 1, ATTN_NORM);
  1124.     stuffcmd (other, "bf\n");
  1125.     other.items = other.items | self.items;
  1126.  
  1127.     if (!coop)
  1128.     {    
  1129.         self.solid = SOLID_NOT;
  1130.         self.model = string_null;
  1131.     }
  1132.  
  1133.     activator = other;
  1134.     SUB_UseTargets();                // fire all targets / killtargets
  1135. };
  1136.  
  1137.  
  1138. void() key_setsounds =
  1139. {
  1140.     if (world.worldtype == 0)
  1141.     {
  1142.         precache_sound ("misc/medkey.wav");
  1143.         self.noise = "misc/medkey.wav";
  1144.     }
  1145.     if (world.worldtype == 1)
  1146.     {
  1147.         precache_sound ("misc/runekey.wav");
  1148.         self.noise = "misc/runekey.wav";
  1149.     }
  1150.     if (world.worldtype == 2)
  1151.     {
  1152.         precache_sound2 ("misc/basekey.wav");
  1153.         self.noise = "misc/basekey.wav";
  1154.     }
  1155. };
  1156.  
  1157. /*QUAKED item_key1 (0 .5 .8) (-16 -16 -24) (16 16 32)
  1158. SILVER key
  1159. In order for keys to work
  1160. you MUST set your maps
  1161. worldtype to one of the
  1162. following:
  1163. 0: medieval
  1164. 1: metal
  1165. 2: base
  1166. */
  1167.  
  1168. void() item_key1 =
  1169. {
  1170.     if (world.worldtype == 0)
  1171.     {
  1172.         precache_model ("progs/w_s_key.mdl");
  1173.         setmodel (self, "progs/w_s_key.mdl");
  1174.         self.netname = "silver key";
  1175.     }
  1176.     else if (world.worldtype == 1)
  1177.     {
  1178.         precache_model ("progs/m_s_key.mdl");
  1179.         setmodel (self, "progs/m_s_key.mdl");
  1180.         self.netname = "silver runekey";
  1181.     }
  1182.     else if (world.worldtype == 2)
  1183.     {
  1184.         precache_model2 ("progs/b_s_key.mdl");
  1185.         setmodel (self, "progs/b_s_key.mdl");
  1186.         self.netname = "silver keycard";
  1187.     }
  1188.     key_setsounds();
  1189.     self.touch = key_touch;
  1190.     self.items = IT_KEY1;
  1191.     setsize (self, '-16 -16 -24', '16 16 32');
  1192.     StartItem ();
  1193. };
  1194.  
  1195. /*QUAKED item_key2 (0 .5 .8) (-16 -16 -24) (16 16 32)
  1196. GOLD key
  1197. In order for keys to work
  1198. you MUST set your maps
  1199. worldtype to one of the
  1200. following:
  1201. 0: medieval
  1202. 1: metal
  1203. 2: base
  1204. */
  1205.  
  1206. void() item_key2 =
  1207. {
  1208.     if (world.worldtype == 0)
  1209.     {
  1210.         precache_model ("progs/w_g_key.mdl");
  1211.         setmodel (self, "progs/w_g_key.mdl");
  1212.         self.netname = "gold key";
  1213.     }
  1214.     if (world.worldtype == 1)
  1215.     {
  1216.         precache_model ("progs/m_g_key.mdl");
  1217.         setmodel (self, "progs/m_g_key.mdl");
  1218.         self.netname = "gold runekey";
  1219.     }
  1220.     if (world.worldtype == 2)
  1221.     {
  1222.         precache_model2 ("progs/b_g_key.mdl");
  1223.         setmodel (self, "progs/b_g_key.mdl");
  1224.         self.netname = "gold keycard";
  1225.     }
  1226.     key_setsounds();
  1227.     self.touch = key_touch;
  1228.     self.items = IT_KEY2;
  1229.     setsize (self, '-16 -16 -24', '16 16 32');
  1230.     StartItem ();
  1231. };
  1232.  
  1233.  
  1234.  
  1235. /*
  1236. ===============================================================================
  1237.  
  1238. END OF LEVEL RUNES
  1239.  
  1240. ===============================================================================
  1241. */
  1242.  
  1243. void() sigil_touch =
  1244. {
  1245. local entity    stemp;
  1246. local float        best;
  1247.  
  1248.     if (other.classname != "player")
  1249.         return;
  1250.     if (other.health <= 0)
  1251.         return;
  1252.  
  1253.     centerprint (other, "You got the rune!");
  1254.  
  1255.     sound (other, CHAN_ITEM, self.noise, 1, ATTN_NORM);
  1256.     stuffcmd (other, "bf\n");
  1257.     self.solid = SOLID_NOT;
  1258.     self.model = string_null;
  1259.     serverflags = serverflags | (self.spawnflags & 15);
  1260.     self.classname = "";        // so rune doors won't find it
  1261.     
  1262.     activator = other;
  1263.     SUB_UseTargets();                // fire all targets / killtargets
  1264. };
  1265.  
  1266.  
  1267. /*QUAKED item_sigil (0 .5 .8) (-16 -16 -24) (16 16 32) E1 E2 E3 E4
  1268. End of level sigil, pick up to end episode and return to jrstart.
  1269. */
  1270.  
  1271. void() item_sigil =
  1272. {
  1273.     if (!self.spawnflags)
  1274.         objerror ("no spawnflags");
  1275.  
  1276.     precache_sound ("misc/runekey.wav");
  1277.     self.noise = "misc/runekey.wav";
  1278.  
  1279.     if (self.spawnflags & 1)
  1280.     {
  1281.         precache_model ("progs/end1.mdl");
  1282.         setmodel (self, "progs/end1.mdl");
  1283.     }
  1284.     if (self.spawnflags & 2)
  1285.     {
  1286.         precache_model2 ("progs/end2.mdl");
  1287.         setmodel (self, "progs/end2.mdl");
  1288.     }
  1289.     if (self.spawnflags & 4)
  1290.     {
  1291.         precache_model2 ("progs/end3.mdl");
  1292.         setmodel (self, "progs/end3.mdl");
  1293.     }
  1294.     if (self.spawnflags & 8)
  1295.     {
  1296.         precache_model2 ("progs/end4.mdl");
  1297.         setmodel (self, "progs/end4.mdl");
  1298.     }
  1299.     
  1300.     self.touch = sigil_touch;
  1301.     setsize (self, '-16 -16 -24', '16 16 32');
  1302.     StartItem ();
  1303. };
  1304.  
  1305. /*
  1306. ===============================================================================
  1307.  
  1308. POWERUPS
  1309.  
  1310. ===============================================================================
  1311. */
  1312.  
  1313. void() powerup_touch;
  1314. void() random_regen;
  1315.  
  1316. void() powerup_touch =
  1317. {
  1318. local entity    stemp;
  1319. local float        best;
  1320.  
  1321.     if (other.classname != "player")
  1322.         return;
  1323.     if (other.health <= 0)
  1324.         return;
  1325.  
  1326.     sprint (other, "You got the ");
  1327.     sprint (other, self.netname);
  1328.     sprint (other,"\n");
  1329.  
  1330.     if (deathmatch)
  1331.     {
  1332.         self.mdl = self.model;
  1333.         
  1334.         if (self.classname == "item_random_powerup")
  1335.         {
  1336.             self.nextthink = time + 30;
  1337.             self.think = random_regen;
  1338.         }
  1339.         else 
  1340.         {
  1341.             if ((self.classname == "item_artifact_invulnerability") ||
  1342.                 (self.classname == "item_artifact_invisibility"))
  1343.                 self.nextthink = time + 60*5;
  1344.             else
  1345.                 self.nextthink = time + 60;
  1346.         
  1347.             self.think = SUB_regen;
  1348.         }
  1349.     }    
  1350.  
  1351.     sound (other, CHAN_VOICE, self.noise, 1, ATTN_NORM);
  1352.     stuffcmd (other, "bf\n");
  1353.     self.solid = SOLID_NOT;
  1354.     other.items = other.items | self.items;
  1355.     self.model = string_null;
  1356.  
  1357. // do the apropriate action
  1358. //    if (self.classname == "item_artifact_envirosuit")
  1359.     if (self.netname == "Biosuit")
  1360.     {
  1361.         other.rad_time = 1;
  1362.         other.radsuit_finished = time + 30;
  1363.     }
  1364.     
  1365. //    if (self.classname == "item_artifact_invulnerability")
  1366.     if (self.netname == "Pentagram of Protection")
  1367.     {
  1368.         other.invincible_time = 1;
  1369.         other.invincible_finished = time + 30;
  1370.     }
  1371.     
  1372. //    if (self.classname == "item_artifact_invisibility")
  1373.     if (self.netname == "Ring of Shadows")
  1374.     {
  1375.         other.invisible_time = 1;
  1376.         other.invisible_finished = time + 30;
  1377.     }
  1378.  
  1379. //    if (self.classname == "item_artifact_super_damage")
  1380.     if (self.netname == "Quad Damage")
  1381.     {
  1382.         other.super_time = 1;
  1383.         other.super_damage_finished = time + 30;
  1384.     }    
  1385.  
  1386.     activator = other;
  1387.     SUB_UseTargets();                // fire all targets / killtargets
  1388. };
  1389.  
  1390.  
  1391.  
  1392. /*QUAKED item_artifact_invulnerability (0 .5 .8) (-16 -16 -24) (16 16 32)
  1393. Player is invulnerable for 30 seconds
  1394. */
  1395. void() item_artifact_invulnerability =
  1396. {
  1397.     self.touch = powerup_touch;
  1398.  
  1399.     precache_model ("progs/invulner.mdl");
  1400.     precache_sound ("items/protect.wav");
  1401.     precache_sound ("items/protect2.wav");
  1402.     precache_sound ("items/protect3.wav");
  1403.     self.noise = "items/protect.wav";
  1404.     setmodel (self, "progs/invulner.mdl");
  1405.     self.netname = "Pentagram of Protection";
  1406.     self.items = IT_INVULNERABILITY;
  1407.     setsize (self, '-16 -16 -24', '16 16 32');
  1408.     StartItem ();
  1409. };
  1410.  
  1411. /*QUAKED item_artifact_envirosuit (0 .5 .8) (-16 -16 -24) (16 16 32)
  1412. Player takes no damage from water or slime for 30 seconds
  1413. */
  1414. void() item_artifact_envirosuit =
  1415. {
  1416.     self.touch = powerup_touch;
  1417.  
  1418.     precache_model ("progs/suit.mdl");
  1419.     precache_sound ("items/suit.wav");
  1420.     precache_sound ("items/suit2.wav");
  1421.     self.noise = "items/suit.wav";
  1422.     setmodel (self, "progs/suit.mdl");
  1423.     self.netname = "Biosuit";
  1424.     self.items = IT_SUIT;
  1425.     setsize (self, '-16 -16 -24', '16 16 32');
  1426.     StartItem ();
  1427. };
  1428.  
  1429.  
  1430. /*QUAKED item_artifact_invisibility (0 .5 .8) (-16 -16 -24) (16 16 32)
  1431. Player is invisible for 30 seconds
  1432. */
  1433. void() item_artifact_invisibility =
  1434. {
  1435.     self.touch = powerup_touch;
  1436.  
  1437.     precache_model ("progs/invisibl.mdl");
  1438.     precache_sound ("items/inv1.wav");
  1439.     precache_sound ("items/inv2.wav");
  1440.     precache_sound ("items/inv3.wav");
  1441.     self.noise = "items/inv1.wav";
  1442.     setmodel (self, "progs/invisibl.mdl");
  1443.     self.netname = "Ring of Shadows";
  1444.     self.items = IT_INVISIBILITY;
  1445.     setsize (self, '-16 -16 -24', '16 16 32');
  1446.     StartItem ();
  1447. };
  1448.  
  1449.  
  1450. /*QUAKED item_artifact_super_damage (0 .5 .8) (-16 -16 -24) (16 16 32)
  1451. The next attack from the player will do 4x damage
  1452. */
  1453. void() item_artifact_super_damage =
  1454. {
  1455.     self.touch = powerup_touch;
  1456.  
  1457.     precache_model ("progs/quaddama.mdl");
  1458.     precache_sound ("items/damage.wav");
  1459.     precache_sound ("items/damage2.wav");
  1460.     precache_sound ("items/damage3.wav");
  1461.     self.noise = "items/damage.wav";
  1462.     setmodel (self, "progs/quaddama.mdl");
  1463.     self.netname = "Quad Damage";
  1464.     self.items = IT_QUAD;
  1465.     setsize (self, '-16 -16 -24', '16 16 32');
  1466.     StartItem ();
  1467. };
  1468.  
  1469.  
  1470. /*
  1471. ===============================================================================
  1472.  
  1473. PLAYER BACKPACKS
  1474.  
  1475. ===============================================================================
  1476. */
  1477.  
  1478. void() BackpackTouch =
  1479. {
  1480.     local string    s;
  1481.     local    float    best, old, new;
  1482.     local        entity    stemp;
  1483.     local    float    acount;
  1484.     
  1485.     if (other.classname != "player")
  1486.         return;
  1487.     if (other.health <= 0)
  1488.         return;
  1489.         
  1490. //ZOID--
  1491.     // Don't let the owner pick up his own backpack for a second.
  1492.     if ((other == self.owner) && ((self.nextthink - time) > 119))
  1493.         return;
  1494. //--ZOID
  1495.  
  1496.     acount = 0;
  1497.     sprint (other, "You get ");
  1498.  
  1499.     if (self.items)
  1500.         if ((other.items & self.items) == 0)
  1501.         {
  1502.             acount = 1;
  1503.             sprint (other, "the ");
  1504.             sprint (other, self.netname);
  1505.         }
  1506.  
  1507. // if the player was using his best weapon, change up to the new one if better
  1508.     stemp = self;
  1509.     self = other;
  1510.     best = W_BestWeapon();
  1511.     self = stemp;
  1512.  
  1513. // change weapons
  1514.     other.ammo_shells1 = other.ammo_shells1 + self.ammo_shells1;
  1515.     other.ammo_nails1 = other.ammo_nails1 + self.ammo_nails1;
  1516.     other.ammo_rockets1 = other.ammo_rockets1 + self.ammo_rockets1;
  1517.     other.ammo_cells1 = other.ammo_cells1 + self.ammo_cells1;
  1518.  
  1519.     other.ammo_lava_nails = other.ammo_lava_nails + self.ammo_lava_nails;
  1520.     other.ammo_multi_rockets = other.ammo_multi_rockets +
  1521.                                     self.ammo_multi_rockets;
  1522.     other.ammo_plasma = other.ammo_plasma + self.ammo_plasma;
  1523.     
  1524.     new = self.items;
  1525.     if (!new)
  1526.         new = other.weapon;
  1527.     old = other.items;
  1528.     other.items = other.items | new;
  1529.     
  1530.     bound_other_ammo ();
  1531.  
  1532.     if (self.ammo_shells1)
  1533.     {
  1534.         if (acount)
  1535.             sprint(other, ", ");
  1536.         acount = 1;
  1537.         s = ftos(self.ammo_shells1);
  1538.         sprint (other, s);
  1539.         sprint (other, " shells");
  1540.     }
  1541.     if (self.ammo_nails1)
  1542.     {
  1543.         if (acount)
  1544.             sprint(other, ", ");
  1545.         acount = 1;
  1546.         s = ftos(self.ammo_nails1);
  1547.         sprint (other, s);
  1548.         sprint (other, " nails");
  1549.     }
  1550.     if (self.ammo_rockets1)
  1551.     {
  1552.         if (acount)
  1553.             sprint(other, ", ");
  1554.         acount = 1;
  1555.         s = ftos(self.ammo_rockets1);
  1556.         sprint (other, s);
  1557.         sprint (other, " rockets");
  1558.     }
  1559.     if (self.ammo_cells1)
  1560.     {
  1561.         if (acount)
  1562.             sprint(other, ", ");
  1563.         acount = 1;
  1564.         s = ftos(self.ammo_cells1);
  1565.         sprint (other, s);
  1566.         sprint (other, " cells");
  1567.     }
  1568.     if (self.ammo_lava_nails)
  1569.     {
  1570.         if (acount)
  1571.             sprint(other, ", ");
  1572.         acount = 1;
  1573.         s = ftos(self.ammo_lava_nails);
  1574.         sprint (other, s);
  1575.         sprint (other, " lava nails");
  1576.     }
  1577.     if (self.ammo_multi_rockets)
  1578.     {
  1579.         if (acount)
  1580.             sprint(other, ", ");
  1581.         acount = 1;
  1582.         s = ftos(self.ammo_multi_rockets);
  1583.         sprint (other, s);
  1584.         sprint (other, " multi rockets");
  1585.     }
  1586.     if (self.ammo_plasma)
  1587.     {
  1588.         if (acount)
  1589.             sprint(other, ", ");
  1590.         acount = 1;
  1591.         s = ftos(self.ammo_plasma);
  1592.         sprint (other, s);
  1593.         sprint (other, " plasma balls");
  1594.     }
  1595.     
  1596.     sprint (other, "\n");
  1597. // backpack touch sound
  1598.     sound (other, CHAN_ITEM, "weapons/lock4.wav", 1, ATTN_NORM);
  1599.     stuffcmd (other, "bf\n");
  1600.  
  1601. // remove the backpack, change self to the player
  1602.     remove(self);
  1603.     self = other;
  1604.  
  1605. // fixme -- move this to after weapon choice if problematic.
  1606.     EnableComboWeapons ( self );
  1607.  
  1608. // change to the weapon
  1609.     if (!deathmatch)
  1610.         self.weapon = new;
  1611.     else
  1612.         Deathmatch_Weapon (old, new);
  1613.  
  1614. //    EnableComboWeapons ( self );
  1615.     UpdateAmmoCounts (self);
  1616.     
  1617.     W_SetCurrentAmmo ();
  1618. };
  1619.  
  1620. /*
  1621. ===============
  1622. DropBackpack
  1623. ===============
  1624. */
  1625. void() DropBackpack =
  1626. {
  1627.     local entity    item;
  1628.  
  1629.     // this is to compensate for the new way we're hacking the ammo
  1630.     // counts. If they're monsters, just copy shells->shells1 etc.
  1631.     if (self.flags & FL_MONSTER)
  1632.     {
  1633.         self.ammo_shells1 = self.ammo_shells;
  1634.         self.ammo_nails1 = self.ammo_nails;
  1635.         self.ammo_rockets1 = self.ammo_rockets;
  1636.         self.ammo_cells1 = self.ammo_cells;
  1637.     }
  1638.     
  1639.     if (!(self.ammo_shells1 + self.ammo_nails1 + self.ammo_rockets1 + 
  1640.             self.ammo_cells1 + self.ammo_lava_nails + self.ammo_multi_rockets))
  1641.         return;    // nothing in it
  1642.  
  1643.     item = spawn();
  1644.     item.origin = self.origin - '0 0 24';
  1645.     
  1646.     item.items = self.weapon;
  1647.     if (item.items == IT_AXE)
  1648.         item.netname = "Axe";
  1649.     else if (item.items == IT_SHOTGUN)
  1650.         item.netname = "Shotgun";
  1651.     else if (item.items == IT_SUPER_SHOTGUN)
  1652.         item.netname = "Double-barrelled Shotgun";
  1653.     else if (item.items == IT_NAILGUN)
  1654.         item.netname = "Nailgun";
  1655.     else if (item.items == IT_SUPER_NAILGUN)
  1656.         item.netname = "Super Nailgun";
  1657.     else if (item.items == IT_GRENADE_LAUNCHER)
  1658.         item.netname = "Grenade Launcher";
  1659.     else if (item.items == IT_ROCKET_LAUNCHER)
  1660.         item.netname = "Rocket Launcher";
  1661.     else if (item.items == IT_LIGHTNING)
  1662.         item.netname = "Thunderbolt";    
  1663.     else if (item.items == IT_LAVA_NAILGUN)
  1664.     {
  1665.         item.netname = "Lava Nail Gun";    
  1666.         item.items = IT_NAILGUN;
  1667.     }
  1668.     else if (item.items == IT_LAVA_SUPER_NAILGUN)
  1669.     {
  1670.         item.netname = "Super Lava Nail Gun";    
  1671.         item.items = IT_SUPER_NAILGUN;
  1672.     }
  1673.     else if (item.items == IT_MULTI_GRENADE)
  1674.     {
  1675.         item.netname = "Multi Grenade Launcher";    
  1676.         item.items = IT_GRENADE_LAUNCHER;
  1677.     }
  1678.     else if (item.items == IT_MULTI_ROCKET)
  1679.     {
  1680.         item.netname = "Multi Rocket Launcher";    
  1681.         item.items = IT_ROCKET_LAUNCHER;
  1682.     }
  1683.     else if (item.items == IT_PLASMA_GUN)
  1684.     {
  1685.         item.netname = "Plasma Gun";    
  1686.         item.items = IT_LIGHTNING;
  1687.     }
  1688.     else
  1689.         item.netname = "";
  1690.     
  1691.     item.ammo_shells1 = self.ammo_shells1;
  1692.     item.ammo_nails1 = self.ammo_nails1;
  1693.     item.ammo_rockets1 = self.ammo_rockets1;
  1694.     item.ammo_cells1 = self.ammo_cells1;
  1695.     item.ammo_lava_nails = self.ammo_lava_nails;
  1696.     item.ammo_multi_rockets = self.ammo_multi_rockets;
  1697.     item.ammo_plasma = self.ammo_plasma;
  1698.     
  1699.     item.velocity_z = 300;
  1700.     item.velocity_x = -100 + (random() * 200);
  1701.     item.velocity_y = -100 + (random() * 200);
  1702.     
  1703.     item.flags = FL_ITEM;
  1704.     item.solid = SOLID_TRIGGER;
  1705.     item.movetype = MOVETYPE_TOSS;
  1706.     setmodel (item, "progs/backpack.mdl");
  1707.     setsize (item, '-16 -16 0', '16 16 56');
  1708.     item.touch = BackpackTouch;
  1709.     
  1710.     item.nextthink = time + 120;    // remove after 2 minutes
  1711.     item.think = SUB_Remove;
  1712. };
  1713.